      SUBROUTINE QUIKVIS5X(ELEMS,UTARG,SUNPOS,
     *       VISTIME,NEEDALL,REQMTMA,IERR)
      IMPLICIT REAL*8 (A-H,O-Z)
C
C THIS ROUTINE IS PART OF THE QUIKVIS PROGRAM.  IT COMPUTES THE TARGET
C AVAILIBILITY TIME.  QUIKVIS5X IS THE HEART OF THE QUIKVIS PROGRAM.
C
C
C VARIABLE DIM TYPE I/O DESCRIPTION
C -------- --- ---- --- -----------
C
C ELEMS     5   R*8  I  ORBITAL ELEMENTS. ORDER IS SMA, ECC, INCL, RAAN,
C                       ARGP. MAY BE IN ANY CONVENIENT COORD SYSTEM.
C                       IN KM AND RADIANS.
C
C UTARG     3   R*8  I  UNIT VECTOR TO THE TARGET. IN THE SAME COORD SYS
C                       AS ELEMS. NO ERROR CHECK FOR UNITY.
C
C SUNPOS    3   R*8  I  SUN POSITION FOR USE WHEN ORBIT NIGHT
C                       REQUIREMENT IS ON. IN THE SAME SYSTEM AS ELEMS.
C                       IN KM.
C
C VISTIME   1   R*8  O  NUMBER SECONDS PER ORBIT THAT THE TARGET
C                       SATISFIES ALL REQUIREMENTS FOR THE GIVEN ELEMS
C                       AND SUNPOS.
C
C NEEDALL   1   L*4  I  FLAG INDICATING WHETHER THE REQMTMA ARRAY IS TO
C                       BE LOADED.
C                       = T, LOAD IT.
C                       = F, DO NOT LOAD IT. MAY SAVE TIME IF DATA IS
C                            NOT NEEDED.
C
C REQMTMA       R*8  O  WHEN NEEDALL=.TRUE., REQMTMA(1,I) CONTAINS THE
C      2,MAXREQMT       MEAN ANOMALY WHERE THE I'TH REQUIREMENT BEGINS
C                       TO BE SATISFIED.  REQMTMA(2,I) IS THE MEAN
C                       ANOMALY WHERE IT CEASES TO BE SATISFIED.  IF
C                       A REQUIREMENT OPTION IF OFF, THE 0,2PI RANGE IS
C                       RETURNED.
C
C                       SECOND INDEX REFERS TO:
C                        I=1 MEAN ANOMALY RANGE WHERE OCCULTATION DUE
C                            TO SOLID EARTH PLUS HORIZON AVOIDANCE IS
C                            SATISFIED
C                        I=2 MEAN ANOMALY RANGE WHERE ORBIT NIGHT REQMT
C                            IS SATISFIED
C                        I=3 MEAN ANOMALY RANGE WHERE VELOCITY VECTOR
C                            AVOIDANCE REQMT IS SATISFIED
C                        I=4 MEAN ANOMALY RANGE WHERE MAX TARGET/ZENITH
C                            SEPARATION REQMT IS SATISFIED
C
C                       WHEN NEEDALL=.FALSE., REQMTMA IS NOT REFERENCED.
C
C IERR      1   I*4  O  ERROR RETURN FLAG
C                        =0, NO ERROR
C                        =OTHERWISE, ERROR.
C
C***********************************************************************
C
C BY C PETRUZZO/GFSC/742.   2/86.
C       MODIFIED.... 9/86. CJP. EXTENSIVE CHANGES TO REFLECT THE CHANGE
C                               FROM WORKING IN TRUE ANOMALY TO WORKING
C                               IN MEAN ANOMALY;  MISC CHANGES FOR
C                               CLEARER CODE.
C                    3/87. CJP. MODIFIED ANGLAP CALL TO REFLECT MOD TO
C                               ANGLAP CALLING SEQUENCE.
C
C***********************************************************************
C
      INCLUDE 'QUIKVIS.INC'
C
      REAL*8 SEGSIN(2,MAXREQMT),SEGSOUT(2,MAXREQMT)
      REAL*8 REQMTMA(2,MAXREQMT)
C
      REAL*8 SUNPOS(3),ELEMS(6),UTARG(3)
      LOGICAL ZEROVIS,NEEDALL
C
C
      IBUG = 0
      LUBUG = 19
C
C
      IF(IBUG.NE.0) THEN
        CALL XYZSPH(-1,RASUN,DECSUN,DUM,SUNPOS,1.D0)
        CALL XYZSPH(-1,RATARG,DECTARG,DUM,UTARG,1.D0)
        WRITE(LUBUG,7501)
     *   ELEMS(1),ELEMS(2),(ELEMS(I)*DEGRAD,I=3,6),
     *   PERIOD/60.D0,RATARG*DEGRAD,DECTARG*DEGRAD,
     *   SUNPOS,RASUN*DEGRAD,DECSUN*DEGRAD,DOREQMT(2),EAVOID*DEGRAD,
     *   VAVOID*DEGRAD,ZMAXSEP*DEGRAD
 7501   FORMAT(
     *    ' QUIKVIS5X DEBUG. INPUT VALUES....'/,
     *    '   ELEMS=',2(T12,3G13.5/),
     *    '   PERIOD=',F6.2,'  RATARG,DECTARG=',2F8.2/,
     *    '   SUNPOS=',3G13.5,'  RA,DEC=',2F8.2/,
     *    '   DOREQMT(2)= ',L2,'   EAVOID=',F8.2,'   VAVOID=',F8.2,
     *           '   ZMAXSEP= ',F8.2)
        END IF
C
      IERR = 0
C
C ***********************************************************
C *  COMPUTE MEAN ANOMALIES WHERE AVAILABILITY BEGINS/ENDS  *
C ***********************************************************
C
      ZEROVIS = .FALSE.
C
C*** DO THE REQUIREMENTS ONE-BY-ONE
C
      DO 9000 IREQ = 1,MAXREQMT
C
C    SET KALLID INDICATING WHICH SUBROUTINE IS NEEDED. IF THE IREQ'TH
C    REQUIREMENT IS NOT INVOLVED, SET KALLID TO ZERO.
C
      KALLID = 0
      IF(DOREQMT(IREQ)) THEN    ! DOREQMT WAS SET IN QUIKVIS0A
        IF(IREQ.EQ.1) THEN
C        REQMT IS OCCULTATION AND HORIZON AVOIDANCE
          KALLID = 1  ! USE TAVISPAK
          KREQMT = 1
          ANGREQ = EAVOID
        ELSE IF(IREQ.EQ.2) THEN
C        ORBIT NIGHT
          KALLID = 2  ! USE SHADTA
        ELSE IF(IREQ.EQ.3) THEN
C        REQMT IS VEL VEC AVOIDANCE
          KALLID = 1  ! USE TAVISPAK
          KREQMT = 2
          ANGREQ = VAVOID
        ELSE IF(IREQ.EQ.4) THEN
C        REQMT IS MAX ZENITH ZEPARATION
          KALLID = 1  ! USE TAVISPAK
          KREQMT = 3
          ANGREQ = ZMAXSEP
        ELSE
          STOP ' QUIKVIS5X. CODING ERROR. STOP 1.'
          END IF
        END IF
C
C    IF IREQ'TH REQUIREMENT IS NOT INVOLVED, AVAILABILITY FOR THIS
C    REQUIREMENT IS 'ALWAYS'.
C
      IF(KALLID.EQ.0) THEN
        KWHENOK = 1    ! ALWAYS OK
        END IF
C
C    IF THERE IS A REQUIREMENT, COMPUTE WHERE IN THE ORBIT THE
C    TARGET IS AVAILABLE.
C
C
      IF(KALLID.EQ.1) THEN
C
        CALL TAVISPAK(KREQMT,ELEMS,UTARG,ANGREQ,KVISFLAG,VISIN,VISOUT,
     *        LUERR,IERR)
        KWHENOK = KVISFLAG   ! =-1, NEVER; =0, SOMETIMES; =+1, ALWAYS
C
C      TAVISPAK RETURNS VISIN/VISOUT MEASURED FROM ASCENDING NODE.  MAKE
C      THEM RELATIVE TO PERIGEE.  IT, MAKE THEM TRUE ANOMALIES.
        VISIN =  VISIN  - ELEMS(5)
        VISOUT = VISOUT - ELEMS(5)
C
        IF(IBUG.NE.0) WRITE(LUBUG,7521) IREQ,KVISFLAG,
     *                   VISIN*DEGRAD,VISOUT*DEGRAD
 7521   FORMAT(' QUIKVIS5X DEBUG 7521. IREQ=',I2,'  TAVISPAK ',
     *             'RETURNS KVISFLAG=',I2/,
     *         '    VISIN-ARGP,VISOUT-ARGP=',2G13.5)
        END IF
C
C
      IF(KALLID.EQ.2) THEN
C
        KUMB = 1   ! SHADTA COMPUTES UMBRA ENTRY AND EXIT TRUE ANOMALIES
        CALL SHADTA(ELEMS,SUNPOS,KUMB,-1,UMBIN,UMBOUT,DUM,DUM,
     *          LUERR,IERR)
C
        IF(IBUG.NE.0) WRITE(LUBUG,7529) IREQ,
     *            KUMB,UMBIN*DEGRAD,UMBOUT*DEGRAD
 7529   FORMAT(' QUIKVIS5X DEBUG 7529. IREQ=',I2,
     *      '  SHADTA RETURNS KUMB=',I2,'    UMBIN,UMBOUT=',2G13.5)
C
        IF(IERR.NE.0) THEN
C        FORCE A LOOK AT WHY ERROR OCCURRED. SHOULD NEVER HAPPEN.
          STOP 'QUIKVIS5X. ERROR STOP 2. SEE CODE.'
          END IF
C
        IF(KUMB.EQ.2) THEN
          KWHENOK = 0       ! SOMETIMES IN ORBIT NIGHT
          VISIN =  UMBIN
          VISOUT = UMBOUT
        ELSE
          KWHENOK = -1      ! NEVER IN ORBIT NIGHT
          END IF
        END IF
C
C
C    WRAP UP PROCESSING FOR THIS REQUIREMENT.  (1) SET 'NEVER SATISFIED'
C    AND 'ALWAYS SATISFIED' START/END MEAN ANOMALIES;  (2) BE SURE
C    ANGLES ARE IN ZERO TO TWOPI RANGE;  (3) CONVERT VISIN AND VISOUT
C    TRUE ANOMALIES TO MEAN ANOMALIES
C
      IF(KWHENOK.EQ.-1) THEN
C      NEVER SATISFIED
        VISIN =  0.D0
        VISOUT = 0.D0
C
      ELSE IF(KWHENOK.EQ.0) THEN
C      SOMETIMES SATISFIED.  BE SURE THEY ARE IN ZERO TO TWOPI RANGE
C      AND CONVERT THEM TO MEAN ANOMALY.
        VISIN =  EQVANG( VISIN  )
        VISOUT = EQVANG( VISOUT )
        IF(ELEMS(2).NE.0.D0) THEN   ! CONVERT TO MEAN ANOMALY.
          VISIN =  ANOMLY(-1,VISIN,ELEMS(2),LUERR,IERR)
          VISOUT = ANOMLY(-1,VISOUT,ELEMS(2),LUERR,IERR)
          END IF
C
      ELSE IF(KWHENOK.EQ.1) THEN
C      ALWAYS SATISFIED
        VISIN =  0.D0
        VISOUT = TWOPI
C
      ELSE
C      ERROR CONDITION. CODING ERROR. BAD KWHENOK VALUE.
        STOP 'QUIKVIS5X. ERROR STOP 3. SEE CODE.'
        END IF
C
C    VISIN AND VISOUT ARE NOW THE MEAN ANOMALIES WHERE THE IREQ'TH
C    REQUIREMENT IS FIRST AND LAST SATISFIED.  STORE THEM IN THE SEGSIN
C    ARRAY FOR USE LATER WHEN THE COMPOSITE OF ALL REQUIREMENTS IS
C    CREATED.
C
      SEGSIN(1,IREQ) = VISIN
      SEGSIN(2,IREQ) = VISOUT
C
C    IF THE NEEDALL FLAG WAS SET, RETURN THE MEAN ANOMALIES IN REQMTMA.
C
      IF(NEEDALL) THEN
        REQMTMA(1,IREQ) = VISIN
        REQMTMA(2,IREQ) = VISOUT
        END IF
C
C    DEBUG
      IF(IBUG.NE.0) WRITE(LUBUG,7522) IREQ,VISIN*DEGRAD,VISOUT*DEGRAD
 7522 FORMAT(' QUIKVIS5X DEBUG 7522.  IREQ=',I3,'  VISIN,VISOUT=',
     *              2G13.5)
C
C    IF THIS REQUIREMENT PRODUCED ZERO AVAILABILITY, THEN SO WILL THE
C    COMPOSITE OF ALL REQUIREMENTS.  IF THE CALLER DOES NOT NEED MEAN
C    ANOMALY IN/OUT INFO FOR EACH REQMT, EXIT THIS LOOP TO AVOID
C    PROCESSING FOR THE REMAINING REQUIREMENTS.
C
      ZEROVIS = ZEROVIS .OR. KWHENOK.EQ.-1
      IF( ZEROVIS .AND. .NOT.NEEDALL ) GO TO 5000
C
C
 9000 CONTINUE
C
C
C *****************************************************************
C *  GET MEAN ANOMALY RANGES WHERE AVAILIABILITY REGIONS OVERLAP  *
C *****************************************************************
C
 5000 CONTINUE
C
C GET MEAN ANOMALY RANGES WHERE ALL REQUIREMENTS ARE SATISFIED.
C NSEGSOUT IS THE NUMBER OF SUCH MEAN ANOMALY SEGMENTS AND SEGSOUT ARE
C THE MEAN ANOMALY VALUES.
C
C
      IF(.NOT.ZEROVIS) THEN
        CALL ANGLAP(SEGSIN,MAXREQMT,SEGSOUT,MAXREQMT,NSEGSOUT,
     *           LUERR,IERR)
        IF(IBUG.NE.0) WRITE(LUBUG,7531)
     *           ((SEGSIN(I,J)*DEGRAD,I=1,2),J=1,MAXREQMT),
     *           NSEGSOUT,((SEGSOUT(I,J)*DEGRAD,I=1,2),J=1,NSEGSOUT)
 7531   FORMAT(' QUIKVIS5X DEBUG 7531. ANGLAP WAS CALLED.'/,
     *           '   SEGSIN=',<MAXREQMT>(T15,2G13.5/),
     *           '   NSEGSOUT=',I2/,
     *           '   SEGSOUT = ',(T12,2G13.5))
        IF(IERR.NE.0) THEN
C        FORCE A LOOK AT WHY ERROR OCCURRED. SHOULD NEVER HAPPEN.
          STOP 'QUIKVIS5X. ERROR STOP 4. SEE CODE.'
          END IF
      ELSE
        NSEGSOUT = 0
        END IF
C
      IF(IBUG.NE.0) WRITE(LUBUG,7541)
     *           NSEGSOUT,((SEGSOUT(I,J)*DEGRAD,I=1,2),J=1,NSEGSOUT)
 7541 FORMAT(' QUIKVIS5X DEBUG 7541. FINAL CONTENTS OF SEGSOUT:'/,
     *       '   NSEGSOUT=',I2/,
     *       '   SEGSOUT = ',(T12,2G13.5))
C
C
C *****************************
C *  TOTAL AVAILABILITY TIME  *
C *****************************
C
      VISTIME = 0.D0
      IF(NSEGSOUT.GT.0) THEN
        ANGTOT = 0.D0
        DO I=1,NSEGSOUT
          TEMP = SEGSOUT(2,I) - SEGSOUT(1,I)
          IF(TEMP.LT.0.D0) TEMP = TWOPI + TEMP
          ANGTOT = ANGTOT + TEMP
          END DO
        VISTIME = ANGTOT/TWOPI * PERIOD
        END IF
C
      IF(IBUG.NE.0) WRITE(LUBUG,7549) VISTIME/60.D0
 7549 FORMAT(' QUIKVIS5X. RETURNING.  VISTIME(MINUTES)=',G13.5)
C
      RETURN
C
C***********************************************************************
C
C
C**** INITIALIZATION CALL. PUT GLOBAL PARAMETER VALUES INTO THIS
C     ROUTINE'S LOCAL VARIABLES.
C
      ENTRY QVINIT5X
C
      CALL QUIKVIS999(-1,R8DATA,I4DATA,L4DATA)
      RETURN
C
C***********************************************************************
C
      END
